home *** CD-ROM | disk | FTP | other *** search
- #include "tmp/postgres.h"
-
- RcsId("$Header: /private/postgres/src/lib/C/RCS/equalfuncs.c,v 1.27 1992/07/26 17:09:30 mer Exp $");
-
- #include "nodes/nodes.h"
- #include "nodes/primnodes.h"
- #include "nodes/relation.h"
- #include "nodes/execnodes.h"
- #include "nodes/plannodes.h"
-
- #include "utils/log.h"
- #include "storage/itemptr.h"
- #include "lib/equalfuncs.h"
-
- bool
- equal(a, b)
- Node a;
- Node b;
- {
- if (a == b)
- return(true);
- if ((!a && b) || (a && !b))
- return(false);
- Assert(IsA(a,Node));
- Assert(IsA(b,Node));
- if (a->type != b->type)
- return (false);
-
- return ((a->equalFunc)(a, b));
- }
-
- /*
- * Stuff from primnodes.h
- */
-
- /*
- * Resdom is a subclass of Node.
- */
-
- bool
- _equalResdom(a, b)
- register Resdom a;
- register Resdom b;
- {
- register OperatorTupleForm at;
- register OperatorTupleForm bt;
-
- if (a->resno != b->resno)
- return (false);
- if (a->restype != b->restype)
- return (false);
- if (a->rescomplex != b->rescomplex)
- return(false);
- if (a->reslen != b->reslen)
- return (false);
- if (strcmp(a->resname, b->resname) != 0)
- return (false);
- if (a->reskey != b->reskey)
- return (false);
-
- /*
- * reskeyop is a pointer to an OperatorTupleForm. We can almost
- * do a bcmp() on the two structures, but the oprname field is
- * a char16, and bytes after the null may not be the same. We
- * do all this by hand because of that.
- */
- at = a->reskeyop;
- bt = b->reskeyop;
-
- /* well, it might happen... */
- if (at == bt)
- return (true);
-
- if (strncmp(at->oprname, bt->oprname, sizeof (bt->oprname)) != 0)
- return (false);
- if (at->oprowner != bt->oprowner)
- return (false);
- if (at->oprprec != bt->oprprec)
- return (false);
- if (at->oprkind != bt->oprkind)
- return (false);
- if (at->oprisleft != bt->oprisleft)
- return (false);
- if (at->oprcanhash != bt->oprcanhash)
- return (false);
- if (at->oprleft != bt->oprleft)
- return (false);
- if (at->oprright != bt->oprright)
- return (false);
- if (at->oprresult != bt->oprresult)
- return (false);
- if (at->oprcom != bt->oprcom)
- return (false);
- if (at->oprnegate != bt->oprnegate)
- return (false);
- if (at->oprlsortop != bt->oprlsortop)
- return (false);
- if (at->oprrsortop != bt->oprrsortop)
- return (false);
- if (at->oprcode != bt->oprcode)
- return (false);
- if (at->oprrest != bt->oprrest)
- return (false);
- if (at->oprjoin != bt->oprjoin)
- return (false);
-
- return (true);
- }
-
- bool
- _equalFjoin(a, b)
- Fjoin a;
- Fjoin b;
- {
- int nNodes;
-
- if (a->fj_initialized != b->fj_initialized)
- return (false);
- if (a->fj_nNodes != b->fj_nNodes)
- return (false);
- if (!equal((Node)a->fj_innerNode, (Node)b->fj_innerNode))
- return (false);
-
- nNodes = a->fj_nNodes;
- if (bcmp(a->fj_results, b->fj_results, nNodes*sizeof(Datum)) != 0)
- return (false);
- if (bcmp(a->fj_alwaysDone, b->fj_alwaysDone, nNodes*sizeof(bool)) != 0)
- return (false);
-
- return(true);
- }
- /*
- * Expr is a subclass of Node.
- */
- bool
- _equalExpr(a, b)
- Expr a;
- Expr b;
- {
- /* no private data */
- return (true);
- }
-
- bool
- _equalIter(a, b)
- Iter a;
- Iter b;
- {
- return (equal((Node)a->iterexpr, (Node)b->iterexpr));
- }
-
- /*
- * Var is a subclass of Expr.
- */
-
- bool
- _equalVar(a, b)
- register Var a;
- register Var b;
- {
- if (!_equalExpr((Expr)a, (Expr)b))
- return (false);
-
- if (a->varno != b->varno)
- return (false);
- if (a->varattno != b->varattno)
- return (false);
- if (a->vartype != b->vartype)
- return (false);
- if (!_equalLispValue(a->varid, b->varid))
- return (false);
-
- return (true);
- }
-
- bool
- _equalArray(a, b)
- register Array a;
- register Array b;
-
- {
- if (!_equalExpr((Expr)a, (Expr)b))
- return (false);
- if (a->arrayelemtype != b->arrayelemtype)
- return (false);
- if (a->arraylow != b->arraylow)
- return (false);
- if (a->arrayhigh != b->arrayhigh)
- return (false);
- if (a->arraylen != b->arraylen)
- return (false);
- return(true);
- }
-
- bool
- _equalArrayRef(a, b)
- register ArrayRef a;
- register ArrayRef b;
-
- {
- if (!_equalExpr((Expr)a, (Expr)b))
- return (false);
- if (a->refelemtype != b->refelemtype)
- return (false);
- if (a->refattrlength != b->refattrlength)
- return (false);
- if (a->refelemlength != b->refelemlength)
- return (false);
- if (a->refelembyval != b->refelembyval)
- return (false);
- if (!_equalLispValue(a->refindexpr, b->refindexpr))
- return (false);
-
- return (_equalLispValue(a->refexpr, b->refexpr));
- }
-
- /*
- * Oper is a subclass of Expr.
- */
-
- bool
- _equalOper(a, b)
- register Oper a;
- register Oper b;
- {
- if (!_equalExpr((Expr)a, (Expr)b))
- return (false);
-
- if (a->opno != b->opno)
- return (false);
- if (a->oprelationlevel != b->oprelationlevel)
- return (false);
- if (a->opresulttype != b->opresulttype)
- return (false);
-
- return (true);
- }
-
- /*
- * Const is a subclass of Expr.
- */
-
- bool
- _equalConst(a, b)
- register Const a;
- register Const b;
- {
- /*
- ** this function used to do a pointer compare on a and b. That's
- ** ridiculous. -- JMH, 7/11/92
- */
- if (a->consttype != b->consttype)
- return(false);
- if (a->constlen != b->constlen)
- return(false);
- if (a->constisnull != b->constisnull)
- return(false);
- if (a->constbyval != b->constbyval)
- return(false);
- return(datumIsEqual(a->constvalue, b->constvalue,
- a->consttype, a->constbyval, a->constlen));
- }
-
- /*
- * Param is a subclass of Expr.
- */
-
- bool
- _equalParam(a, b)
- register Param a;
- register Param b;
- {
- if (!_equalExpr((Expr) a, (Expr) b))
- return (false);
-
- if (a->paramkind != b->paramkind)
- return (false);
- if (a->paramtype != b->paramtype)
- return (false);
- if (!equal((Node)a->param_tlist, (Node)b->param_tlist))
- return (false);
-
- switch (a->paramkind) {
- case PARAM_NAMED:
- case PARAM_NEW:
- case PARAM_OLD:
- if (strcmp(a->paramname, b->paramname) != 0)
- return (false);
- break;
- case PARAM_NUM:
- if (a->paramid != b->paramid)
- return (false);
- break;
- case PARAM_INVALID:
- /*
- * XXX: Hmmm... What are we supposed to return
- * in this case ??
- */
- return(true);
- break;
- default:
- elog(WARN, "_equalParam: Invalid paramkind value: %d",
- a->paramkind);
- }
-
- return (true);
- }
-
- /*
- * Func is a subclass of Expr.
- */
-
- bool
- _equalFunc(a, b)
- register Func a;
- register Func b;
- {
- if (!_equalExpr((Expr) a, (Expr) b))
- return (false);
-
- if (a->funcid != b->funcid)
- return (false);
- if (a->functype != b->functype)
- return (false);
- if (a->funcisindex != b->funcisindex)
- return (false);
- if (a->funcsize != b->funcsize)
- return (false);
- if (!equal((Node)a->func_tlist, (Node)b->func_tlist))
- return (false);
- if (!equal((Node)a->func_planlist, (Node)b->func_planlist))
- return (false);
-
- return (true);
- }
-
- /*
- * CInfo is a subclass of Node.
- */
-
- bool
- _equalCInfo(a,b)
- register CInfo a;
- register CInfo b;
- {
- Assert(IsA(a,CInfo));
- Assert(IsA(b,CInfo));
-
- if (!_equalLispValue((LispValue)(get_clause(a)),
- (LispValue)(get_clause(b))))
- return(false);
- if (a->selectivity != b->selectivity)
- return(false);
- if (a->notclause != b->notclause)
- return(false);
- #ifdef EqualMergeOrderExists
- if (!EqualMergeOrder(a->mergesortorder,b->mergesortorder))
- return(false);
- #endif
- if(a->hashjoinoperator != b->hashjoinoperator)
- return(false);
- return(equal((Node)(a->indexids),
- (Node)(b->indexids)));
- }
-
- bool
- _equalJoinMethod(a,b)
- register JoinMethod a,b;
- {
- Assert(IsA(a,JoinMethod));
- Assert(IsA(b,JoinMethod));
-
- if (!equal((Node)(a->jmkeys),
- (Node)(b->jmkeys)))
- return(false);
- if (!equal((Node)(a->clauses),
- (Node)(b->clauses)))
- return(false);
- return(true);
- }
-
- bool
- _equalPath(a,b)
- register Path a,b;
- {
- Assert(IsA(a,Path));
- Assert(IsA(b,Path));
-
- if (a->pathtype != b->pathtype)
- return(false);
- if (a->parent != b->parent)
- return(false);
- /*
- if (a->path_cost != b->path_cost)
- return(false);
- */
- if (!equal((Node)(a->p_ordering),
- (Node)(b->p_ordering)))
- return(false);
- if (!equal((Node)(a->keys),
- (Node)(b->keys)))
- return(false);
- if (!equal((Node)(a->pathsortkey),
- (Node)(b->pathsortkey)))
- return(false);
- /*
- if (a->outerjoincost != b->outerjoincost)
- return(false);
- */
- if (!equal((Node)(a->joinid),
- (Node)(b->joinid)))
- return(false);
- return(true);
- }
-
- bool
- _equalIndexPath(a,b)
- register IndexPath a,b;
- {
- Assert(IsA(a,IndexPath));
- Assert(IsA(b,IndexPath));
-
- if (!_equalPath((Path)a,(Path)b))
- return(false);
- if (!equal((Node)(a->indexid), (Node)(b->indexid)))
- return(false);
- if (!equal((Node)(a->indexqual), (Node)(b->indexqual)))
- return(false);
- return(true);
- }
-
- bool
- _equalJoinPath(a,b)
- register JoinPath a,b;
- {
- Assert(IsA(a,JoinPath));
- Assert(IsA(b,JoinPath));
-
- if (!_equalPath((Path)a,(Path)b))
- return(false);
- if (!equal((Node)(a->pathclauseinfo), (Node)(b->pathclauseinfo)))
- return(false);
- if (!equal((Node)(a->outerjoinpath), (Node)(b->outerjoinpath)))
- return(false);
- if (!equal((Node)(a->innerjoinpath), (Node)(b->innerjoinpath)))
- return(false);
- return(true);
- }
-
- bool
- _equalMergePath(a,b)
- register MergePath a,b;
- {
- Assert(IsA(a,MergePath));
- Assert(IsA(b,MergePath));
-
- if (!_equalJoinPath((JoinPath)a,(JoinPath)b))
- return(false);
- if (!equal((Node)(a->path_mergeclauses), (Node)(b->path_mergeclauses)))
- return(false);
- if (!equal((Node)(a->outersortkeys), (Node)(b->outersortkeys)))
- return(false);
- if (!equal((Node)(a->innersortkeys), (Node)(b->innersortkeys)))
- return(false);
- return(true);
- }
-
- bool
- _equalHashPath(a,b)
- register HashPath a,b;
- {
- Assert(IsA(a,HashPath));
- Assert(IsA(b,HashPath));
-
- if (!_equalJoinPath((JoinPath)a,(JoinPath)b))
- return(false);
- if (!equal((Node)(a->path_hashclauses), (Node)(b->path_hashclauses)))
- return(false);
- if (!equal((Node)(a->outerhashkeys), (Node)(b->outerhashkeys)))
- return(false);
- if (!equal((Node)(a->innerhashkeys), (Node)(b->innerhashkeys)))
- return(false);
- return(true);
- }
-
- bool
- _equalJoinKey(a,b)
- register JoinKey a,b;
- {
- Assert(IsA(a,JoinKey));
- Assert(IsA(b,JoinKey));
-
- if (!equal((Node)(a->outer),(Node)(b->outer)))
- return(false);
- if (!equal((Node)(a->inner),(Node)(b->inner)))
- return(false);
- return(true);
- }
-
- bool
- _equalMergeOrder(a,b)
- register MergeOrder a,b;
- {
- if (a == (MergeOrder)NULL && b == (MergeOrder)NULL)
- return(true);
- Assert(IsA(a,MergeOrder));
- Assert(IsA(b,MergeOrder));
-
- if (a->join_operator != b->join_operator)
- return(false);
- if (a->left_operator != b->left_operator)
- return(false);
- if (a->right_operator != b->right_operator)
- return(false);
- if (a->left_type != b->left_type)
- return(false);
- if (a->right_type != b->right_type)
- return(false);
- return(true);
- }
-
- bool
- _equalHInfo(a,b)
- register HInfo a,b;
- {
- Assert(IsA(a,HInfo));
- Assert(IsA(b,HInfo));
-
- if (a->hashop != b->hashop)
- return(false);
- return(true);
- }
-
- /* XXX This equality function is a quick hack, should be
- * fixed to compare all fields.
- */
-
- bool
- _equalIndexScan(a,b)
- register IndexScan a,b;
- {
- Assert(IsA(a,IndexScan));
- Assert(IsA(b,IndexScan));
-
- if(a->cost != b->cost)
- return(false);
-
- if (a->fragment != b->fragment)
- return(false);
-
- if (!equal((Node)(a->indxqual),(Node)(b->indxqual)))
- return(false);
-
- if (a->scanrelid != b->scanrelid)
- return(false);
-
- if (!equal((Node)(a->indxid),(Node)(b->indxid)))
- return(false);
- return(true);
- }
-
- bool
- _equalJInfo(a,b)
- register JInfo a,b;
- {
- Assert(IsA(a,JInfo));
- Assert(IsA(b,JInfo));
- if (!equal((Node)(a->otherrels),(Node)(b->otherrels)))
- return(false);
- if (!equal((Node)(a->jinfoclauseinfo),(Node)(b->jinfoclauseinfo)))
- return(false);
- if (a->mergesortable != b->mergesortable)
- return(false);
- if (a->hashjoinable != b->hashjoinable)
- return(false);
- return(true);
- }
- /*
- * Stuff from execnodes.h
- */
-
- /*
- * EState is a subclass of Node.
- */
-
- bool
- _equalEState(a, b)
- register EState a;
- register EState b;
- {
- if (a->es_direction != b->es_direction)
- return (false);
- if (a->es_time != b->es_time)
- return (false);
- if (a->es_owner != b->es_owner)
- return (false);
- if (!_equalLispValue(a->es_locks, b->es_locks))
- return (false);
- if (!_equalLispValue(a->es_subplan_info, b->es_subplan_info))
- return (false);
- if (a->es_error_message == (Name) NULL
- || b->es_error_message == (Name) NULL) {
- if (a->es_error_message != b->es_error_message)
- return (false);
- } else {
- if (strcmp(a->es_error_message, b->es_error_message) != 0)
- return (false);
- }
- if (!_equalLispValue(a->es_range_table, b->es_range_table))
- return (false);
-
- if (!_equalHeapTuple(a->es_qualification_tuple,
- b->es_qualification_tuple))
- return (false);
- if (!ItemPointerEquals(a->es_qualification_tuple_id,
- b->es_qualification_tuple_id))
- return (false);
- if (!_equalRelation(a->es_relation_relation_descriptor,
- b->es_relation_relation_descriptor))
- return (false);
- if (a->es_result_relation_info != b->es_result_relation_info)
- return (false);
-
- return (true);
- }
-
- /*
- * _equalHeapTuple -- Are two heap tuples equal?
- */
-
- bool
- _equalHeapTuple(a, b)
- register HeapTuple a;
- register HeapTuple b;
- {
- if (a->t_len != b->t_len)
- return (false);
- if (!ItemPointerEquals(&a->t_ctid, &b->t_ctid))
- return (false);
-
- /*
- * We ignore the t_lock entry, because i don't know how to
- * decide which entry in the union to look at.
- */
-
- if (a->t_oid != b->t_oid)
- return (false);
- if (a->t_xmin != b->t_xmin)
- return (false);
- if (a->t_cmin != b->t_cmin)
- return (false);
- if (a->t_xmax != b->t_xmax)
- return (false);
- if (a->t_cmax != b->t_cmax)
- return (false);
-
- if (!ItemPointerEquals(&a->t_chain, &b->t_chain))
- return (false);
- if (a->t_tmin != b->t_tmin)
- return (false);
- if (a->t_tmax != b->t_tmax)
- return (false);
- if (a->t_natts != b->t_natts)
- return (false);
- if (a->t_hoff != b->t_hoff)
- return (false);
- if (a->t_vtype != b->t_vtype)
- return (false);
-
- /*
- * We ignore the t_bits field, because i don't know how to
- * compute its length.
- */
-
- return (true);
- }
-
- /*
- * _equalRelation -- Are two relations equal?
- *
- * Two relations are considered equal, for our purposes, if they
- * have the same object id. This may not be sufficient, in which
- * case we can write more code.
- */
-
- bool
- _equalRelation(a, b)
- Relation a;
- Relation b;
- {
- if (a->rd_id != b->rd_id)
- return (false);
-
- return (true);
- }
- /*
- * _equalLispValue -- are two lists equal?
- *
- * This is a comparison by value. It would be simpler to write it
- * to be recursive, but it should run faster if we iterate.
- */
-
- bool
- _equalLispValue(a, b)
- register LispValue a;
- register LispValue b;
- {
- while (a != (LispValue) NULL) {
-
- if (b == (LispValue) NULL)
- return (false);
- if (a == b)
- return(true);
- if (LISP_TYPE(a) != LISP_TYPE(b))
- return (false);
-
- switch (LISP_TYPE(a)) {
-
- case PGLISP_ATOM:
- if (a->val.name != b->val.name)
- return (false);
- break;
-
- case PGLISP_DTPR:
- if (!_equalLispValue(a->val.car, b->val.car))
- return (false);
- break;
-
- case PGLISP_FLOAT:
- if (a->val.flonum != b->val.flonum)
- return (false);
- break;
-
- case PGLISP_INT:
- if (a->val.fixnum != b->val.fixnum)
- return (false);
- break;
-
- case PGLISP_STR:
- if (strcmp(a->val.str, b->val.str) != 0)
- return (false);
- break;
-
- case PGLISP_VECI:
- if (a->val.veci->size != b->val.veci->size)
- return (false);
- if (bcmp(&(a->val.veci->data[0]), &(b->val.veci->data[0]),
- a->val.veci->size) != 0)
- return (false);
- break;
-
- default:
- if (IsA(a,Node) && IsA(b,Node) )
- if(NodeType(a) == NodeType(b)) {
- return((*(a->equalFunc))(a,b));
- } else {
- return(false);
- }
- elog(NOTICE,"equal: LispAtom type %d unknown",
- a->type);
- return (false);
- }
-
- /* next */
- a = CDR(a);
- b = CDR(b);
- }
-
- if (b != (LispValue) NULL)
- return (false);
-
- return (true);
- }
-
- bool
- _equalFragment(a,b)
- register Fragment a,b;
- {
- Assert(IsA(a,Fragment));
- Assert(IsA(b,Fragment));
- if (a->frag_root != b->frag_root)
- return(false);
- if (a->frag_parent_op != b->frag_parent_op)
- return(false);
- if (a->frag_parallel != b->frag_parallel)
- return(false);
- if (!equal((Node)(a->frag_subtrees),(Node)(b->frag_subtrees)))
- return(false);
- if (a->frag_parent_frag != b->frag_parent_frag)
- return(false);
- return(true);
- }
-
-
-
-